﻿using Microsoft.VisualStudio.TestTools.UnitTesting;
using Neitzel.Irc;
using Neitzel.Irc.Client;

namespace Neitzel.Tests
{
    /// <summary>
    /// Tests of the IRC Library.
    /// </summary>
    [TestClass]
    public class IrcLibTests
    {
        /// <summary>
        /// Test the UniversalFlag Class
        /// </summary>
        [TestMethod]
        public void UniversalFlagsTest()
        {
            var flags = new UniversalAttributes();

            // Create new Flags
            flags.Attributes = "abcCdEF";

            // =======================================================
            // SetFlag Tests
            // =======================================================
            // remove "c" (mid of Flag-String)
            flags.SetAttribute('c', false);
            Assert.IsTrue(flags.Attributes == "abCdEF");

            // remove "Z" that is not in there
            flags.SetAttribute('Z', false);
            Assert.IsTrue(flags.Attributes == "abCdEF");

            // add "a" (Already in Flags)
            flags.SetAttribute('a', true);
            Assert.IsTrue(flags.Attributes == "abCdEF");

            // add "Z" (new Flag)
            flags.SetAttribute('Z', true);
            Assert.IsTrue(flags.Attributes == "abCdEFZ");

            // remove "a" (first flag)
            flags.SetAttribute('a', false);
            Assert.IsTrue(flags.Attributes == "bCdEFZ");

            // remove "Z" (last flag)
            flags.SetAttribute('Z', false);
            Assert.IsTrue(flags.Attributes == "bCdEF");

            // Set CaseSensitice to false
            flags.CaseSensitive = false;
            Assert.IsTrue(flags.Attributes == "BCDEF");

            // Ass flag "a" - should be stored as "A"
            flags.SetAttribute('a', true);
            Assert.IsTrue(flags.Attributes == "BCDEFA");

            // =======================================================
            // CheckFlag Tests
            // =======================================================
            flags = new UniversalAttributes();
            flags.Attributes = "abCD";
            Assert.IsTrue(flags.IsSet('a'));
            Assert.IsTrue(flags.IsSet('b'));
            Assert.IsTrue(flags.IsSet('C'));
            Assert.IsTrue(flags.IsSet('D'));
            Assert.IsFalse(flags.IsSet('A'));
            Assert.IsFalse(flags.IsSet('B'));
            Assert.IsFalse(flags.IsSet('c'));
            Assert.IsFalse(flags.IsSet('d'));
            Assert.IsFalse(flags.IsSet('Z'));

            // Test it again without beeing case sensitive.
            flags.CaseSensitive = false;
            Assert.IsTrue(flags.IsSet('A'));
            Assert.IsTrue(flags.IsSet('B'));
            Assert.IsTrue(flags.IsSet('c'));
            Assert.IsTrue(flags.IsSet('d'));

            // =======================================================
            // CheckFlag Tests
            // =======================================================
            flags = new UniversalAttributes();
            flags.Change("-abc+oOIZ");
            Assert.IsTrue(flags.Attributes == "oOIZ");
            flags.Change("-O-I+ab-Z+zZ");
            Assert.IsTrue(flags.Attributes == "oabzZ");
        }

        /// <summary>
        /// Test the IrcConnection
        /// </summary>
        [TestMethod]
        public void IrcConnectionTests()
        {
            using (var con = new IrcConnection())
            {
                Assert.IsFalse(con.Connected);
                con.ServerName = "127.0.0.1";
                con.Port = 6667;
                con.Connect();
                Assert.IsTrue(con.Connected);
                con.Close();
                Assert.IsFalse(con.Connected);
            }
        }

        /// <summary>
        /// Tests for the IrcClientEventTypes enum.
        /// </summary>
        [TestMethod]
        public void IrcClientEventTest()
        {
            IrcClientEventTypes All = IrcClientEventTypes.AllEvents;
            IrcClientEventTypes Error = IrcClientEventTypes.AllErrors;
            IrcClientEventTypes Some = IrcClientEventTypes.ErrorNoSuchServer & IrcClientEventTypes.ErrorNoSuchNick;

            Assert.IsTrue(All.HasFlag(Error));
            Assert.IsFalse(Error.HasFlag(All));
            Assert.IsTrue(Error.HasFlag(Some));
            Assert.IsFalse(Some.HasFlag(Error));
        }
    }
}
